import { Component, OnInit, ViewChild, ChangeDetectionStrategy, ElementRef } from '@angular/core';
import { FieldItem, AdvancedFilterComponent, FilterState, TreeNode } from '@iux/live';
import { FormControl, Validators } from '@angular/forms';

@Component({
  templateUrl: './save-filter.component.html',
  changeDetection: ChangeDetectionStrategy.OnPush,
  styles: [
    `
      .filter-save {
        width: 350px;
        display: flex;
        flex-flow: column;
      }
      .filter-save-title {
        font-size: 12px;
        margin-bottom: 4px;
      }

      .filter-save-input {
        margin-bottom: 16px;
      }

      .filter-save-button-container {
        display: flex;
        align-items: center;
        justify-content: flex-end;
      }

      .filter-save-button:not(:last-child) {
        margin-right: 16px;
      }

      .filter-save-tree {
        display: flex;
        justify-content: space-between;
        align-items: center;
      }

      .filter-save-tree-icon {
        display: flex;
        align-items: center;
      }

      .filter-save-tree-icon i {
        font-size: 16px;
      }

      .filter-save-tree-icon > i:first-child {
        margin-right: 8px;
      }
    `,
  ],
})
export class SaveFilterComponent implements OnInit {
  @ViewChild(AdvancedFilterComponent) AdvancedFilterComponent: AdvancedFilterComponent;
  @ViewChild('filterInput') inputRef: ElementRef;

  public treeData = [
    {
      label: 'Documents',
      children: [
        {
          label: 'Expenses.doc',
          isLeaf: true,
        },
        {
          label: 'Resume.doc',
          isLeaf: true,
        },
      ],
    },
    {
      label: 'Word',
      children: [
        {
          label: 'Expenses.doc',
          isLeaf: true,
        },
        {
          label: 'Resume.doc',
          isLeaf: true,
        },
      ],
    },
    {
      label: 'Pictures',
      children: [
        {
          label: 'logo.png',
          isLeaf: true,
        },
        {
          label: 'banner.pnd',
          isLeaf: true,
        },
      ],
    },
  ];

  public fields: FieldItem[] = [
    {
      label: 'Status',
      field: 'status',
      group: 'software',
      type: 'single',
      option: {
        items: [
          {
            label: 'Normal',
            value: 'normal',
          },
          {
            label: 'Error',
            value: 'error',
          },
          {
            label: 'Creating',
            value: 'creating',
          },
          {
            label: 'Mapping',
            value: 'mapping',
          },
          {
            label: 'Unmapping',
            value: 'unmapping',
          },
          {
            label: 'Deleting',
            value: 'deleting',
          },
          {
            label: 'Expanding',
            value: 'expanding',
          },
        ],
      },
    },
    {
      label: 'Checker',
      field: 'checker',
      group: 'software',
      type: 'multiple',
      option: {
        items: [
          {
            label: 'Jack',
            value: 'Jack',
          },
          {
            label: 'Tom',
            value: 'Tom',
          },
          {
            label: 'Jerry',
            value: 'Jerry',
          },
          {
            label: 'Mary',
            value: 'Mary',
          },
          {
            label: 'Ada',
            value: 'Ada',
          },
          {
            label: 'Clara',
            value: 'Clara',
          },
          {
            label: 'Alberta',
            value: 'Alberta',
          },
          {
            label: 'Agatha',
            value: 'Agatha',
          },
        ],
        lvShowCheckAll: true,
        lvShowFilter: true,
      },
    },
    {
      label: 'Commit Number',
      field: 'commitNumber',
      group: 'software',
      type: 'numberRange',
    },
    {
      label: 'Issue Number',
      field: 'issueNumber',
      group: 'software',
      type: 'number',
    },
    {
      label: 'Release Version',
      field: 'releaseVersion',
      group: 'version',
      type: 'textInput',
      mode: 'startsWith',
    },
    {
      label: 'Date',
      field: 'dateSelection',
      group: 'version',
      type: 'datePicker',
      option: {
        lvPickerMode: 'date',
        lvShowTodayButton: true,
      },
    },
    {
      label: 'Date Range',
      field: 'dateRange',
      group: 'version',
      type: 'dateRangePicker',
      mode: 'rangeIn',
    },
    {
      label: 'Tree Single',
      field: 'treeSingle',
      type: 'treeSingle',
      option: {
        lvData: this.treeData,
      },
    },
    {
      label: 'Tree Multiple',
      field: 'treeMultiple',
      type: 'treeMultiple',
      option: {
        lvData: this.treeData,
        lvShowCheckbox: true,
      },
    },
  ];

  public customFiltersTreeData: TreeNode[] = []; // 自定义筛选模板树数据

  public saveFilterPopVisible: boolean = false; // 保存筛选面板是否显示
  public filterSaveName: FormControl<string>; // 保存筛选输入框
  public filterSaveLimit: number = 15; // 保存筛选输入框最长字符限制
  public customFilters: { [name: string]: FilterState[] }; // 保存的筛选模板数据
  public starCustomFiltersName: string; // 收藏的筛选模板名称

  constructor() {}

  ngOnInit(): void {
    this.filterSaveName = new FormControl('', [Validators.required, Validators.maxLength(this.filterSaveLimit)]);
    this.customFilters = JSON.parse(localStorage.getItem('AdvancedFilterCustomFilters')) || {};
    this.starCustomFiltersName = localStorage.getItem('AdvancedFilterCustomFiltersStar') || '';
    this.setCustomSaveFiltersTreeData();
    setTimeout(() => {
      this.starCustomFiltersName && this.AdvancedFilterComponent.setCustomFilters(this.customFilters[this.starCustomFiltersName]);
    }, 0);
  }

  /**
   * 根据筛选模板设置自定义筛选模板树数据
   */
  setCustomSaveFiltersTreeData(): void {
    if (Object.keys(this.customFilters).length === 0) {
      this.customFiltersTreeData = [];
      return;
    }
    this.customFiltersTreeData = [
      {
        label: '自定义保存筛选',
        expanded: true,
        children: Object.keys(this.customFilters).map((key) => ({
          label: key,
          value: this.customFilters[key],
          isLeaf: true,
        })),
      },
    ];
  }

  /**
   * 点击保存筛选按钮的回调
   */
  onSaveFilter(e: MouseEvent): void {
    e.stopPropagation();
    this.saveFilterPopVisible = true;
    setTimeout(() => {
      this.inputRef?.nativeElement?.focus();
    }, 250); // 打开面板动画结束后自动聚焦
  }

  /**
   * 点击保存筛选面板确认按钮
   */
  onSaveFilterConfirm(): void {
    this.filterSaveName.markAsDirty();
    this.filterSaveName.updateValueAndValidity();

    if (!(this.filterSaveName.invalid && (this.filterSaveName.dirty || this.filterSaveName.touched))) {
      this.saveFilterPopVisible = false;
      this.customFilters[this.filterSaveName.value] = this.AdvancedFilterComponent.getSelectedValue();
      localStorage.setItem('AdvancedFilterCustomFilters', JSON.stringify(this.customFilters));
      this.setCustomSaveFiltersTreeData();
      this.filterSaveName.reset();
    }
  }

  /**
   * 点击保存筛选面板取消按钮
   */
  onSaveFilterCancel(): void {
    this.saveFilterPopVisible = false;
  }

  /**
   * 点击自定义保存筛选面板项
   */
  onTreePanelClick({ node }: { node: TreeNode }): void {
    if (!node.isLeaf) {
      return;
    }
    this.AdvancedFilterComponent.togglePopoverVisible();

    this.AdvancedFilterComponent.setCustomFilters(this.customFilters[node.label]);
  }

  /**
   * 点击自定义保存筛选面板项收藏按钮
   */
  handleCustomFilterStar(e: MouseEvent, label: string): void {
    e.stopPropagation();
    this.starCustomFiltersName = label === this.starCustomFiltersName ? '' : label;
    this.starCustomFiltersName
      ? localStorage.setItem('AdvancedFilterCustomFiltersStar', this.starCustomFiltersName)
      : localStorage.removeItem('AdvancedFilterCustomFiltersStar');
  }

  /**
   * 点击自定义保存筛选面板项删除按钮
   */
  handleCustomFilterDelete(e: MouseEvent, label: string): void {
    e.stopPropagation();

    delete this.customFilters[label];

    if (label === this.starCustomFiltersName) {
      this.starCustomFiltersName = '';
      localStorage.removeItem('AdvancedFilterCustomFiltersStar');
    }

    if (Object.keys(this.customFilters).length === 0) {
      this.customFiltersTreeData = [];
      localStorage.removeItem('AdvancedFilterCustomFilters');
      return;
    }

    localStorage.setItem('AdvancedFilterCustomFilters', JSON.stringify(this.customFilters));
    this.deleteNodeByLabel(this.customFiltersTreeData, label);
    this.customFiltersTreeData = [...this.customFiltersTreeData];
  }

  /**
   * 删除匹配label的子节点，若子节点删除后其父节点为空，父节点删除
   * @param arr 要操作的数据
   * @param label 标签名
   */
  private deleteNodeByLabel(arr: TreeNode[], label: string): void {
    for (let i = arr.length - 1; i >= 0; i--) {
      if (arr[i]?.label === label) {
        arr.splice(i, 1);
        return;
      }

      if (arr[i].children) {
        this.deleteNodeByLabel(arr[i].children, label);
        if (arr[i].children.length === 0) {
          arr.splice(i, 1);
        }
      }
    }
  }
}
